// src/utils/treeDataUtils.ts

import { schema } from '@/ts/base';
import {
  ICompany,
  IDepartment,
  IPerson,
  TargetType,
  orgAuth,
  ITarget,
  ITeam,
} from '@/ts/core';
export type deptItemType = {
  key: string;
  id: string;
  label: string;
  item: schema.XEntity;
  parentId: string | undefined;
  hasItems: boolean;
  children: deptItemType[];
  disabled?: boolean;
  typeName: string;
};
const loadDepartments = <T extends deptItemType>(depts: IDepartment[], parent: T) => {
  depts.forEach((dept) => {
    const item = getTreeNode(dept.metadata, dept.children, parent.key) as T;
    if (item.hasItems) loadDepartments(dept.children, item);
    parent.children.push(item);
  });
};

const findInTree = <T extends { subTarget: T[] }>(
  data: T,
  predicate: (node: T) => boolean,
): T | undefined => {
  // 检查当前节点是否满足条件
  if (predicate(data)) {
    return data;
  }
  for (const child of data.subTarget) {
    const result = findInTree(child, predicate);
    if (result) {
      return result;
    }
  }

  // 如果未找到，返回 undefined
  return undefined;
};

// 获取树节点
export const getTreeNode = <T>(
  data: schema.XEntity,
  children?: ITeam[],
  pid?: string,
): T => {
  return {
    key: `${pid ?? data?.key ?? '0'}_${data.id}`,
    id: data.id,
    parentId: pid,
    label: data.name,
    typeName: data.typeName,
    item: data,
    hasItems: children ? children.length > 0 : false,
    children: [],
  } as unknown as T;
};
const hasTeamAuth = (user: IPerson, teamIds: string[]) => {
  const auths = [orgAuth.SuperAuthId, orgAuth.DataAuthId];
  return user.authenticate(teamIds, auths);
};
const loadTargetTrees = <T extends deptItemType>(target: ITeam) => {
  let childrenItems: ITeam[] = [];
  if (target.typeName === '单位') {
    childrenItems = (target as ICompany).departments;
  } else {
    childrenItems = (target as IDepartment).children;
  }
  const teamNode = getTreeNode<deptItemType>(target.metadata, childrenItems);
  loadDepartments(childrenItems as IDepartment[], teamNode);
  return [teamNode] as T[];
};

// 获取树
export const getTreeDatas = async <T extends deptItemType>(
  target: ITarget,
): Promise<T[]> => {
  const treeNodes: T[] = [];
  //集群成员列表
  if (target.typeName === TargetType.Group) {
    await target.loadMembers();
    treeNodes.push(
      getTreeNode({
        id: target.directory.spaceId,
        key: 'company',
        name: '本单位',
        typeName: '单位',
      } as unknown as schema.XEntity),
      ...target.members.map((member) => getTreeNode<T>(member)),
    );
  } else {
    //单位/部门组织 列表
    const team = target as ICompany | IDepartment;
    //默认权限
    treeNodes.push(getTreeNode({ ...team.user.metadata, name: '本人' }));
    //超管权限
    if (hasTeamAuth(team.user, [team.belongId])) {
      treeNodes.push(...loadTargetTrees<T>(team));
    } else if (team.user.departments.length > 0) {
      const departments = team.user.departments.filter(
        (dept) => dept.belongId === team.directory.spaceId,
      );
      for (const depart of departments) {
        //部分部门管理员权限
        if (hasTeamAuth(team.user, [depart.id])) {
          const predicate = (node: ITarget) =>
            node.typeName === depart.typeName && node.id === depart.id;
          const _data = findInTree(team as ITarget, predicate);
          if (_data) {
            treeNodes.push(...loadTargetTrees<T>(_data));
          }
        }
      }
    }
  }

  //无管理权

  return treeNodes;
};
// 获取集群组织树
